package edu.ccut.saturn.workflow.finishTaskModule.code;

import java.sql.Connection;
import java.sql.SQLException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;

import edu.ccut.saturn.component.DefaultComponent;
import edu.ccut.saturn.component.IParameterContext;
import edu.ccut.saturn.component.SaturnData;
import edu.ccut.saturn.operation.Operation;
import edu.ccut.saturn.workflow.common.Constants;
import edu.ccut.saturn.workflow.common.WorkFlowTools;
import edu.ccut.saturn.workflow.model.ActivityInfo;
import edu.ccut.saturn.workflow.model.WorkFlowInfo;

public class FinishManualActivity extends DefaultComponent {
	@Override
	public void execute(IParameterContext parameterContext) throws Exception {
		WorkFlowInfo workFlowInfo = (WorkFlowInfo) parameterContext
		.getParameterValue(0);
		SaturnData currentActivityInstance = (SaturnData)parameterContext.getParameterValue(1);
		SaturnData workitemInstance = (SaturnData)parameterContext.getParameterValue(2);
		
		ActivityInfo currentActivityInfo = workFlowInfo.getActivityInfoById(currentActivityInstance.get("activity_id")+"");
		Connection conn = parameterContext.getConnection();
		String activity_instance_id = currentActivityInstance.get("activity_instance_id")+"";
		String workflow_instance_id = currentActivityInstance.get("process_instance_id")+"";
		String workitem_id = workitemInstance.get("workitem_id")+"";
		boolean isfinish = false;//当前活动是否完成
		// 判断是否更新活动实例表的状态
		if (currentActivityInfo.getIsMulWorkItems().equals(
				Constants.ACTIVITY_ISMULWORKITEMS)) {
			updateActivityStateFinish(conn, activity_instance_id);
			isfinish = true;
		} else {
			//工作项总个数
			int allCount = getWorkItemAllCount(conn, workflow_instance_id,
					activity_instance_id);
			//完成个数
			int finishCount = getWorkItemFinishCount(conn, workflow_instance_id,
					activity_instance_id);
			if (currentActivityInfo.getIsFinishAll().equals(
					Constants.ACTIVITY_WORKITEM_FINISHALL)) {
				if (allCount == finishCount) {
					updateActivityStateFinish(conn, activity_instance_id);
					isfinish =true;
				}
			} else {
				int finishRequiredNum = Integer.parseInt(currentActivityInfo
						.getFinishRequiredNum());
				if (finishRequiredNum > 0) {
					if (finishCount >= finishRequiredNum) {
						updateActivityStateFinish(conn, activity_instance_id);
						updateWorkItemStateABORTED(conn, workflow_instance_id,
								activity_instance_id,workitem_id);
						//删除剩余工作项参与者
						isfinish =true;
					}
				}

				double finishRequiredPercent = Double.parseDouble(currentActivityInfo
						.getFinishRequiredPercent());
				if (finishRequiredPercent > 0) {
					double c = Double.parseDouble(String.valueOf(finishCount));
					double d = Double.parseDouble(String.valueOf(allCount));
					if ((c / d) * 100 >= finishRequiredPercent) {
						updateActivityStateFinish(conn, activity_instance_id);
						updateWorkItemStateABORTED(conn, workflow_instance_id,
								activity_instance_id,workitem_id);
						isfinish =true;
					}
				}
			}
		}
		parameterContext.setParameter(3, isfinish);
	}

	private void updateActivityStateFinish(Connection conn,
			String activity_instance_id) throws Exception {
		/*SaturnData activityInstance = WorkFlowTools.getActivityInstance();
		
		activityInstance.set("state", Constants.ACTIVITY_STATE_FINISH);
		activityInstance.set("end_time", Operation.baseService().GetSystemTime());
		activityInstance.set("activity_instance_id", activity_instance_id);
		
		Operation.dataBase().updateByPrimaryKey(activityInstance, "", conn);*/
		
		String sys_time = Operation.baseService().GetSystemTime();
		SaturnData activityInstance = Operation.dataBase().queryByPrimaryKey(Constants.SATURNDATA_WF_ACTIVITY_INSTANCE,
				activity_instance_id, conn);
	    SaturnData activityInstanceForUpdate = WorkFlowTools.getActivityInstance();
	    activityInstanceForUpdate.set("state", Constants.ACTIVITY_STATE_FINISH);
	    activityInstanceForUpdate.set("end_time", sys_time);
	    activityInstanceForUpdate.set("activity_instance_id", activity_instance_id);
		
		String is_timeout = activityInstance.getString("is_timeout");
		if(is_timeout!=null&&!"".equals(is_timeout)){
			String final_time = activityInstance.get("final_time")+""; 
			SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
			Long timeout_number = format.parse(sys_time).getTime() - format.parse(final_time).getTime();
			activityInstanceForUpdate.set("timeout_number", timeout_number);
		}
		Operation.dataBase().updateByPrimaryKey(activityInstanceForUpdate, "", conn);
	}
	/**
	 * 查询一个流程实例中一个活动中工作项总个数
	 * 
	 * @param conn
	 * @param workFlowInstanceId
	 * @param activityInstanceId
	 * @return
	 * @throws SQLException
	 */
	private int getWorkItemAllCount(Connection conn, String workFlowInstanceId,
			String activityInstanceId) throws Exception {
		int count = 0;

		HashMap<String,Object> paramMap = new HashMap<String,Object>();
		paramMap.put("process_instance_id", workFlowInstanceId);
		paramMap.put("activity_instance_id", activityInstanceId);
		ArrayList<SaturnData> result = Operation.dataBase().queryBySaturnSql(
				Constants.SATURNDATA_WF_COUNT, 
				"GET_COUNT_WORKITEMS_IN_ACTIVITY", paramMap, conn);
		
		if(result!=null){
			count = Integer.parseInt(result.get(0).get("count")+"");
		}
		
		return count;
	}
	/**
	 * 查询一个流程实例中一个活动中工作项完成个数,任务取消也算完成 
	 * 
	 * @param conn
	 * @param workFlowInstanceId
	 * @param activityInstanceId
	 * @return
	 * @throws SQLException
	 */
	private int getWorkItemFinishCount(Connection conn,
			String workFlowInstanceId, String activityInstanceId)
			throws Exception {
		int count = 0;
		
		HashMap<String,Object> paramMap = new HashMap<String,Object>();
		paramMap.put("process_instance_id", workFlowInstanceId);
		paramMap.put("activity_instance_id", activityInstanceId);
		ArrayList<SaturnData> result = Operation.dataBase().queryBySaturnSql(
				Constants.SATURNDATA_WF_COUNT, "GET_COUNT_FINISHED_WORKITEMS_IN_ACTIVITY", paramMap, conn);
		
		if(result!=null){
			count = Integer.parseInt(result.get(0).get("count")+"");
		}
		
		return count;
	}
	/**
	 * 更新剩余工作项为取消
	 * 
	 * @throws SQLException
	 */
	private void updateWorkItemStateABORTED(Connection conn,
			String workFlowInstanceId, String activityInstanceId,String workitem_id)
			throws Exception {
		/*String sql = "update WF_WORKITEM_INSTANCE set STATE=" 
				+ Constants.WORKITEM_STATE_ABORTED + ","; 
		sql = sql + "END_TIME=to_date('" + Operation.baseService().GetSystemTime()
				+ "','YYYY-MM-DD HH24:MI:SS') where PROCESS_INSTANCE_ID=" 
				+ workFlowInstanceId + " and ACTIVITY_INSTANCE_ID=" 
				+ activityInstanceId + " and workitem_id <>"+workitem_id+" and STATE<>" 
				+ Constants.WORKFLOW_STATE_FINISH  ;
		Operation.dataBase().updateBySQL(sql, conn);*/
		
		SaturnData workitemInstance = WorkFlowTools.getWorkItemInstance();	
		workitemInstance.set("state", Constants.WORKITEM_STATE_ABORTED);
		workitemInstance.set("end_time",Operation.baseService().GetSystemTime());
	
		String condition = "where process_instance_id=" 
			+ workFlowInstanceId + " and activity_instance_id=" 
			+ activityInstanceId + " and workitem_id <>"+workitem_id+" and STATE<>" 
			+ Constants.WORKFLOW_STATE_FINISH ;
		
		Operation.dataBase().updateByCondition(workitemInstance, condition, "", conn);
	}
}